using System;
using System.Collections.Generic;
using System.Text;
using DslFactory.Utilities.DteCodeModel;

namespace Dslfactory.wcfLanguage
{
 public partial class Interface
 {
  /// <summary>
  /// Get the KindLabel property value as a function of the interface
  /// being a ServiceContract or not.
  /// </summary>
  /// <returns></returns>
  internal string GetKindLabelValue()
  {
   if (IsServiceContract)
    return "Service contract";
   else
    return "Interface";
  }

  /// <summary>
  /// Find a method of given signature
  /// </summary>
  /// <param name="signature"></param>
  /// <returns></returns>
  public Method FindMethod(string signature)
  {
   return Methods.Find(delegate(Method m) { return m.Signature == signature; });
  }

  /// <summary>
  ///  Find the method having "unique signature" in the sense of CodeFunction.get_Prototype(vsCMPrototype.)
  /// </summary>
  /// <param name="methodUniqueSignature"></param>
  /// <returns></returns>
  internal Method FindMethodHavingUniqueSignature(string methodUniqueSignature)
  {
   // Verify parenthesis
   int indexBeginningOfParameters = methodUniqueSignature.IndexOf('(');
   int indexEndOfParametes = methodUniqueSignature.LastIndexOf(')');
   if ((indexBeginningOfParameters == -1) || (indexEndOfParametes == -1))
    throw new ArgumentException(string.Format("Method signature '{0}' is incorrect : missing parenthesis", methodUniqueSignature));

   string methodFullName = methodUniqueSignature.Substring(0, indexBeginningOfParameters);
   string name = methodFullName;
   int lastDot = methodFullName.LastIndexOf('.');
   if (lastDot != -1)
    name = methodFullName.Substring(lastDot + 1);
   string signature =  name + " "+methodUniqueSignature.Substring(indexBeginningOfParameters).Replace(",", ", ");

   // Find the method having "unique signature" in the sense of get_Prototype()
   foreach (Method m in Methods)
    if (m.Signature.EndsWith(signature))
     return m;
   return null;
  }

  /// <summary>
  /// Get the services definition this interface belongs to
  /// </summary>
  /// <returns></returns>
  protected internal override ServicesDefinition GetServicesDefinition()
  {
   return ServicesDefinition;
  }

  /// <summary>
  /// Show the concepts that are used by this concept
  /// </summary>
  public override void ShowUsedConcepts()
  {
  }

 }

 public partial class ServiceContract
 {
  public override void ShowUsedConcepts()
  {
   foreach (Method method in Methods)
   {
    string name;
    string returnType;
    List<KeyValuePair<string, string>> parameters;
    MethodLabel.ParsePrototype(method.Prototype, out name, out returnType, out parameters);

    // Add reference to return type
    AddReferenceToTypeIfPossible(returnType);

    // And to each parameter
    foreach(KeyValuePair<string, string> parameter in parameters)
     AddReferenceToTypeIfPossible(parameter.Value);
   }
  }

  private void AddReferenceToTypeIfPossible(string fullyQualifiedTypeName)
  {
   DataClass dataClass = ShowIfPossible(fullyQualifiedTypeName) as DataClass;
   if ((dataClass != null) && (!ReferencedDataClasses.Contains(dataClass)))
    ReferencedDataClasses.Add(dataClass);
  }
 }
}
